home *** CD-ROM | disk | FTP | other *** search
- ;===============================================================================
- ;
- ;FICHERO: GIFASM.ASM
- ;
- ;AUTOR: ANTONIO LADESA JURADO
- ;
- ;FECHA: 24/6/94
- ;
- ;DESCRIPCION:
- ;
- ; Fichero que contiene las constantes, variables y funciones
- ; para la compresión LZW de ficheros GIF.
- ;
- ; Extraido del libro Bit-Mapped Graphics y modificado para posibilitar
- ; la grabación de una imagen de más de 64k.
- ; Para ello, se lee la imagen desde disco.
- ;
- ;
- ;===============================================================================
-
-
- BUFFERSIZE EQU 255
- MAXMAX EQU 4096 ;CODIGO MAXIMO + 1
-
- STRUCTSIZE EQU 32
- HASHFIRST EQU 0 ;DESPLAZAMIENTOS EN LA TABLA DE MASCARAS
- HASHNEXT EQU 2
- HASHCHAR EQU 4
- _AOFF EQU 6
-
- ;SEGMENTO DE DATOS
- SEGDATOS MACRO
- PUSH AX
- MOV AX,_DATA
- MOV DS,AX
- POP AX
- ENDM
-
- ;SEGMENTO EXTRA
- EXTRASEG MACRO
- PUSH AX
- MOV AX,_DATA
- MOV ES,AX
- POP AX
- ENDM
-
- GIFENC_TEXT SEGMENT BYTE PUBLIC 'CODE'
- ASSUME CS:GIFENC_TEXT,DS:_DATA
-
- ;----- FUNCION: int LZWescribir(GIFdatos *gd) ----------------------------------
- ;
- ; Descripción:
- ;
- ; Esta función comprime y graba en disco una imagen cuyos datos aparecen en la
- ; estructura gd.
- ;
- ; Parámetros:
- ;
- ; GIFdatos *gd : puntero a estructura que contiene los datos de la imagen
- ;
- ; Retorno:
- ;
- ; 1:error creacion de fichero
- ; 2:error escritura cabecera
- ; 3:error datos
- ; 4:error cierre fichero
- ;
- ;-------------------------------------------------------------------------------
-
- PUBLIC _LZWescribir
- _LZWescribir PROC FAR
- PUSH BP
- MOV BP,SP
-
- MOV DI,OFFSET STARTINIT
- MOV AX,_DATA
- MOV ES,AX
- MOV CX,ENDINIT-STARTINIT
- CLD
- MOV AL,0
- REPNE STOSB
-
- MOV SI,[BP+_AOFF+0]
- MOV DS,[BP+_AOFF+2]
- EXTRASEG
- MOV DI,OFFSET GIFSTRUCT
- MOV CX,STRUCTSIZE
- CLD
- REPNE MOVSB
-
- SEGDATOS
-
- MOV CX,BITS
- MOV AX,1
- SHL AX,CL
-
- MOV CLEAR,AX
- INC AX
- MOV EOI,AX
- INC AX
- MOV FIRSTFREE,AX
-
- CALL FOPEN
- CALL FCREATE
- JNC PACK1
- MOV AX,0001H
- JMP PACKX
-
- PACK1: CALL HEADER
- JNC PACK2
- CALL FCLOSE
- MOV AX,0002H
- JMP PACKX
-
- PACK2: CALL COMPRESS
- CALL FOOTER
- JNC PACK3
- CALL FCLOSE
- MOV AX,0003H
- JMP PACKX
-
- PACK3: CALL FCLOSE
- JNC PACK4
- MOV AX,0004H
- JMP PACKX
-
- PACK4: MOV AX,0
-
- PACKX: POP BP
- RET
-
- _LZWescribir ENDP
-
-
- ; ESCRIBIR LA CABECERA
- HEADER PROC NEAR
- MOV DX,OFFSET GIFHEAD
- MOV CX,6
- CALL FWRITE
- MOV AX,SCREENWIDE
- CALL FPUTW
- MOV AX,SCREENDEEP
- CALL FPUTW
- MOV AX,BITS
- DEC AX
- OR AL,90H
- CALL FPUTC
- MOV AX,BACKGROUND
- CALL FPUTC
- MOV AL,00H
- CALL FPUTC
-
- MOV AX,1
- MOV CX,BITS
- SHL AX,CL
- MOV CX,3
- MUL CX
-
- MOV CX,AX
- MOV DX,PALETTEOFF
- PUSH DS
- MOV DS,PALETTESEG
- CALL FWRITE
- POP DS
- MOV AL,','
- CALL FPUTC
- MOV AX,IMAGELEFT
- CALL FPUTW
- MOV AX,IMAGETOP
- CALL FPUTW
- MOV AX,IMAGEWIDE
- CALL FPUTW
- MOV AX,IMAGEDEEP
- CALL FPUTW
-
- MOV AX,BITS
- DEC AX
- CALL FPUTC
-
- MOV AX,BITS
- CALL FPUTC
- RET
- HEADER ENDP
-
- FOOTER PROC NEAR
- MOV AL,0
- CALL FPUTC
- MOV AL,3BH
- CALL FPUTC
- RET
- FOOTER ENDP
-
-
- ; COMPRIME LA IMAGEN
- COMPRESS PROC NEAR
- CALL INIT_TABLE
- MOV AX,CLEAR
- CALL WRITE_CODE
- CALL FGETCH
- L4: XOR AH,AH
- L4A: MOV PREFIXCODE,AX
- CALL FGETCH
- JC L17
- MOV THISBYTE,AL
- MOV BX,PREFIXCODE
- CALL LOOKUP_CODE
- JNC L4A
- CALL ADD_CODE
- PUSH BX
- MOV AX,PREFIXCODE
- CALL WRITE_CODE
- POP BX
- MOV AL,THISBYTE
- CMP BX,MAXCODE
- JL L4
- CMP NBITS,12
- JL L14
- MOV AX,CLEAR
- CALL WRITE_CODE
- CALL INIT_TABLE
- MOV AL,THISBYTE
- JMP L4
-
- L14: INC NBITS
- SHL MAXCODE,1
- JMP L4
-
- L17: MOV AX,PREFIXCODE
- CALL WRITE_CODE
- MOV AX,EOI
- CALL WRITE_CODE
- MOV AX,BITOFFSET
- CMP AX,0
- JE L18
- MOV CX,8
- XOR DX,DX
- DIV CX
- OR DX,DX
- JE L17A
- INC AX
-
- L17A: CALL FLUSH
- L18: RET
- COMPRESS ENDP
-
-
- ; INICIALIZAR LA TABLA
-
- INIT_TABLE PROC NEAR
- MOV AX,BITS
- INC AX
- MOV NBITS,AX
-
- MOV AX,CLEAR
- SHL AX,1
- MOV MAXCODE,AX
-
- MOV AX,CLEAR
- PUSH ES
- EXTRASEG
- MOV CX,5
- MUL CX
- MOV CX,AX
- MOV AX,-1
- MOV DI,OFFSET HASH
- REP STOSW
- POP ES
- MOV AX,FIRSTFREE
- MOV FREECODE,AX
- RET
- INIT_TABLE ENDP
-
-
- ; ESCRIBIR UN CODIGO
- WRITE_CODE PROC NEAR
- PUSH AX
- MOV AX,BITOFFSET
- MOV CX,NBITS
- ADD BITOFFSET,CX
- MOV CX,8
- XOR DX,DX
- DIV CX
- CMP AX,BUFFERSIZE-4
- JL WC1
- CALL FLUSH
- PUSH DX
- ADD DX,NBITS
- MOV BITOFFSET,DX
- POP DX
- ADD AX,OFFSET OUTPUTDATA
- MOV SI,AX
- MOV AL,BYTE PTR [SI]
- MOV OUTPUTDATA,AL
- XOR AX,AX
- WC1: ADD AX,OFFSET OUTPUTDATA
- MOV DI,AX
- POP AX
- MOV CX,DX
- XOR DX,DX
- JCXZ WC3
- WC2: SHL AX,1
- RCL DX,1
- LOOP WC2
- OR AL,BYTE PTR [DI]
- WC3: PUSH ES
- EXTRASEG
- STOSW
- MOV AL,DL
- STOSB
- POP ES
- RET
- WRITE_CODE ENDP
-
-
- FLUSH PROC NEAR
- PUSH AX
- PUSH BX
- PUSH CX
- PUSH DX
- MOV ONEBYTE,AL
-
- MOV BX,HANDLE
- MOV DX, OFFSET ONEBYTE
- MOV CX,AX
- INC CX
- MOV AX,4000H
- INT 21H
-
- POP DX
- POP CX
- POP BX
- POP AX
- RET
- FLUSH ENDP
-
- ; LEER UN BYTE DEL BLOQUE DE DATOS
- FGETCH PROC NEAR
- CMP SIZEMSB,0
- JNE FGETCH0
- CMP SIZELSB,0
- JNE FGETCH0
-
- STC
- RET
-
- FGETCH0: PUSH BX
- PUSH CX
- PUSH DX
- MOV AX,3F00H
- MOV BX,ORIGEN
- MOV CX,1
- MOV DX, OFFSET LEIDO
- INT 21H
- MOV AL,DS:LEIDO
- POP DX
- POP CX
- POP BX
-
- FGETCH1: CMP SIZELSB,0
- JE FGETCH2
- DEC SIZELSB
- JMP FGETCH3
-
- FGETCH2: DEC SIZEMSB
- DEC SIZELSB
-
-
- FGETCH3: CLC
- RET
- FGETCH ENDP
-
-
- ; ENCONTRAR UN CODIGO EN LA TABLA
- LOOKUP_CODE PROC NEAR
- CALL INDEX
- MOV DI,0
- CMP BYTE PTR [SI+HASHFIRST],-1
- JE GC4
- INC DI
- MOV BX,[SI+HASHFIRST]
- GC2: CALL INDEX
- CMP [SI+HASHCHAR],AL
- JNE GC3
- CLC
- MOV AX,BX
- RET
- GC3: CMP WORD PTR [SI+HASHNEXT],-1
- JE GC4
- MOV BX,[SI+HASHNEXT]
- JMP GC2
- GC4: STC
- RET
- LOOKUP_CODE ENDP
-
-
- ; CONVERTIR INDICE EN DIRECCION
- INDEX PROC NEAR
- MOV SI,BX
- SHL SI,1
- SHL SI,1
- ADD SI,BX
- ADD SI,OFFSET HASH
- RET
- INDEX ENDP
-
-
- ;INSERTAR CODIGO EN LA TABLA
- ADD_CODE PROC NEAR
- MOV BX,FREECODE
- CMP DI,0
- JE AC1
- MOV [SI+HASHNEXT],BX
- JMP AC2
- AC1: MOV [SI+HASHFIRST],BX
- AC2: CMP BX,MAXMAX
- JE AC3
- CALL INDEX
- MOV WORD PTR [SI+HASHFIRST],-1
- MOV WORD PTR [SI+HASHNEXT],-1
- MOV [SI+HASHCHAR],AL
- INC FREECODE
- AC3: RET
- ADD_CODE ENDP
-
-
- ; CREAR FICHERO GIF VACIO
- FCREATE PROC NEAR
- PUSH DS
- MOV DX,DESTINOOFF
- MOV DS,DESTINOSEG
-
- MOV AX,3C00H
- MOV CX,0000H
- INT 21H
- POP DS
- MOV HANDLE,AX
- RET
- FCREATE ENDP
-
-
- ; CREAR FICHERO GIF VACIO
- FOPEN PROC NEAR
- PUSH DS
- PUSH DX
- MOV DX,ORIGENOFF
- MOV DS,ORIGENSEG
-
- MOV AX,3D00H
- INT 21H
- POP DX
- POP DS
- MOV ORIGEN,AX
- RET
- FOPEN ENDP
-
-
- ;ESCRIBIR CX BYTES EN EL FICHERO
- FWRITE PROC NEAR
- PUSH DS
- SEGDATOS
- MOV BX,HANDLE
- POP DS
- MOV AX,4000H
- INT 21H
- RET
- FWRITE ENDP
-
-
- ;ESCRIBIR EL BYTE DE AL EN EL FICHERO
- FPUTC PROC NEAR
- MOV ONEBYTE,AL
- MOV AX,4000H
- MOV BX,HANDLE
- MOV CX,0001H
- MOV DX,OFFSET ONEBYTE
- INT 21H
- RET
- FPUTC ENDP
-
-
- ;ESCRIBIR LA PALABRA DE AX EN EL FICHERO
- FPUTW PROC NEAR
- PUSH AX
- CALL FPUTC
- POP AX
- MOV AL,AH
- CALL FPUTC
- RET
- FPUTW ENDP
-
-
- ;CERRAR LOS FICHEROS
- FCLOSE PROC NEAR
- MOV AX,3E00H
- MOV BX,HANDLE
- INT 21H
-
- MOV AX,3E00H
- MOV BX,ORIGEN
- INT 21H
-
- RET
- FCLOSE ENDP
-
- GIFENC_TEXT ENDS
-
- DGROUP GROUP _DATA,_BSS
- _DATA SEGMENT WORD PUBLIC 'DATA'
-
- GIFHEAD DB 'GIF87a'
-
- STARTINIT LABEL BYTE
- GIFSTRUCT LABEL BYTE
- SCREENWIDE DW ?
- SCREENDEEP DW ?
- IMAGELEFT DW ?
- IMAGETOP DW ?
- IMAGEWIDE DW ?
- IMAGEDEEP DW ?
- BACKGROUND DW ?
- BITS DW ?
- SIZELSB DW ?
- SIZEMSB DW ?
- PALETTEOFF DW ?
- PALETTESEG DW ?
- ORIGENOFF DW ?
- ORIGENSEG DW ?
- DESTINOOFF DW ?
- DESTINOSEG DW ?
-
- CLEAR DW 0
- EOI DW 0
- FIRSTFREE DW 0
- PREFIXCODE DW 0
- FREECODE DW 0
- MAXCODE DW 0
- NBITS DW 0
- THISBYTE DB 0
- BITOFFSET DW 0
- HANDLE DW 0
- ORIGEN DW 0
- LEIDO DB 0
- ONEBYTE DB 0
- OUTPUTDATA DB BUFFERSIZE DUP (0)
-
- HASH DB 20480 DUP (0)
- ENDINIT LABEL BYTE
-
- _DATA ENDS
-
- _BSS SEGMENT WORD PUBLIC 'BSS'
- _BSS ENDS
- END
-